package com.liveinstars.im.api.impl;

import com.liveinstars.im.util.BadWordUtil;
import com.liveinstars.api.im.BadWordRecognizeService;
import com.liveinstars.api.im.vo.WordBadLevel;
import com.liveinstars.im.api.BadWordTransferService;
import com.liveinstars.im.domain.dao.model.Badword;
import com.liveinstars.im.domain.manager.BadwordManager;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Map;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

/**
 * 对内容进行过滤，查找违规词的功能实现
 * cache中没有的话，从file中获取并更新过去，cache中有的话，读取cache中的值
 * 修改也修改cache中的值，并更新树
 */
@Service
public class BadWordRecognizeApiServiceApiImpl implements BadWordRecognizeService,BadWordTransferService {

    private static final Logger LOGGER = LoggerFactory.getLogger(BadWordRecognizeApiServiceApiImpl.class);

    public static final String CONTENT = "content";
    public static final String NEED_SHADOW = "needShadow";

    @Autowired
    private BadwordManager badwordManager;

    public int apolloRefreshTab = 1;

    private int refreshTab;

    private ExecutorService initTreeService = Executors.newFixedThreadPool(3);

    @Override
    public WordBadLevel getWordBadLevel(Map params) {
        LOGGER.info("getWordBadLevel {} {} {}", refreshTab, apolloRefreshTab, params.get(CONTENT));
        initBadWordTreeAsync();
        String content = "";
        Boolean needShadow = false;
        if(params.containsKey(CONTENT)) {
            content = (String) params.get(CONTENT);
            if(params.containsKey(NEED_SHADOW)) {
                needShadow = (Boolean) params.get(NEED_SHADOW);
            }
        }
        return BadWordUtil.getWordBadLevel(content, needShadow);
    }


    @Override
    public String getBadWordList() {
        LOGGER.info("getBadWordList");
        LOGGER.info("getBadWordList {} {}", refreshTab, apolloRefreshTab);
        BadWordCollect badWordCollect = new BadWordCollect().invoke();
        String eroticismStr = badWordCollect.getEroticismStr();
        String reactionStr = badWordCollect.getReactionStr();
        String otherStr = badWordCollect.getOtherStr();
        StringBuilder stringBuilder = new StringBuilder();
        stringBuilder.append(eroticismStr).append(reactionStr).append(otherStr);
        return stringBuilder.toString();
    }

    @Override
    public String addOrDeleteBadWord(String word, String type) {
        return "";
    }

    @Override
    public String transferWordsToHealth(String content) {
        LOGGER.info("transferWordsToHealth {} {} {}", refreshTab, apolloRefreshTab);
        initBadWordTreeAsync();

        return BadWordUtil.transferToHealth(content);
    }

    @Override
    public int scoreWordHealth(String content) {
        LOGGER.info("transferWordsToHealth {} {} {}", refreshTab, apolloRefreshTab);
        initBadWordTreeAsync();

        WordBadLevel wordBadLevel = BadWordUtil.getWordBadLevel(content, false);
        LOGGER.info("transferWordsToHealth {} {} {}", refreshTab, apolloRefreshTab);
        return wordBadLevel.getScore();
    }

    private void initBadWordTreeAsync() {
        if(refreshTab != apolloRefreshTab){
            synchronized (this) {
                if(refreshTab != apolloRefreshTab) {

                    initTreeService.execute(() -> {

                        BadWordCollect badWordCollect = new BadWordCollect().invoke();
                        String eroticismStr = badWordCollect.getEroticismStr();
                        String reactionStr = badWordCollect.getReactionStr();
                        String otherStr = badWordCollect.getOtherStr();
                        LOGGER.info("getWordBadLevel initTreeService execute");
                        BadWordUtil.refreshTree(eroticismStr, reactionStr, otherStr);
                    });
                    refreshTab = apolloRefreshTab;
                }
            }
        }
    }

    private class BadWordCollect {
        private String eroticismStr;
        private String reactionStr;
        private String otherStr;

        public String getEroticismStr() {
            return eroticismStr;
        }

        public String getReactionStr() {
            return reactionStr;
        }

        public String getOtherStr() {
            return otherStr;
        }

        public BadWordCollect invoke() {
            List<Badword> badwords = badwordManager.listAll();
            StringBuilder eroticisms = new StringBuilder();
            StringBuilder reactions = new StringBuilder();
            StringBuilder others = new StringBuilder();
            for(Badword badWord : badwords){
                switch (badWord.getType()){
                    case 1:
                        others.append(badWord.getBadword() + "\n");
                        break;
                    case 2:
                        eroticisms.append(badWord.getBadword() + "\n");
                        break;
                    case 3:
                        reactions.append(badWord.getBadword() + "\n");
                        break;
                }

            }
            eroticismStr = eroticisms.toString();
            reactionStr = reactions.toString();
            otherStr = others.toString();
            return this;
        }
    }
}
